import java.util.PriorityQueue;


class TimerTask implements Comparable<TimerTask>{
    //时间
    private long time;
    //运行方法
    private Runnable runnable;
    //构造方法
    public TimerTask(Runnable runnable,int delay){
        this.runnable = runnable;
        this.time = System.currentTimeMillis()+delay;
    }
    //获取时间
    public long getTime() {
        return time;
    }
    //run方法，用来执行任务
    public void run(){
        runnable.run();
    }
    //compareTo方法，指定比较方式
    @Override
    public int compareTo(TimerTask o) {
        return (int) (this.time-o.time);
    }
}
class Timer {
    //要有一个线程不停处理任务
    private Thread t  = null;
    //以优先级队列存储时间任务
    private PriorityQueue<TimerTask> queue = new PriorityQueue<>();
    private Object locker = new Object();
    public void schdule(Runnable runnable,int delay){
        synchronized (locker) {
            TimerTask task = new TimerTask(runnable, delay);
            queue.offer(task);
            locker.notify();
        }
    }

    public Timer(){
        t = new Thread(()-> {
            synchronized (locker) {
                while (true) {
                    try {
                   while(queue.isEmpty()) {
                        //这里需要阻塞
                        locker.wait();
                    }
                    TimerTask task = queue.peek();
                    long curTime = System.currentTimeMillis();
                    if (task.getTime() >= curTime) {
                        task.run();
                        queue.poll();
                    } else {
                        //这里同样需要阻塞
                        locker.wait(curTime - task.getTime());
                    }
                }catch (InterruptedException e){
                        e.printStackTrace();
                    }
                }
            }
           });
        t.start();
    }
}
public class ThreadDemo3 {
    public static void main(String[] args) {
        Timer timer = new Timer();
        timer.schdule(new Runnable() {
            @Override
            public void run() {
                System.out.println("hello 3000");
            }
        },3000);
        timer.schdule(new Runnable() {
            @Override
            public void run() {
                System.out.println("hello 2000");
            }
        },2000);
        timer.schdule(new Runnable() {
            @Override
            public void run() {
                System.out.println("hello 1000");
            }
        },1000);
    }
}
